﻿using System;
using System.Collections.Concurrent;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using System.Text;
using System.Threading.Tasks;
using UnityPay.Core.DTO;

namespace UnityPay.Core.Utils
{
    public interface IService: BankPayActionInterface
    {

    }
    /// <summary>
    /// 抽象服务类
    /// </summary>
    public abstract class AbstractService : IService
    {
        public BankMsgDTO IcbcRefund(string orderid, string amount, string Refundid)
        {
            throw new NotImplementedException();
        }
        public BankMsgDTO IcbcRefundQuery(string orderid, string Refundid)
        {
            throw new NotImplementedException();
        }
        public BankMsgDTO Pay(string amount, string qrcode, string orderid, string goodsname)
        {
            throw new NotImplementedException();
        }
        public BankMsgDTO Query(string orderid, string qrcodetype)
        {
            throw new NotImplementedException();
        }
        public string Refund(string CUST_ID, string USER_ID, string PASSWORD, string orderid, string amount, string Refundid)
        {
            throw new NotImplementedException();
        }
        public BankMsgDTO ZfbWxOrderClose(string orderid, string qrcodetype)
        {
            throw new NotImplementedException();
        }
        public BankMsgDTO ZfbWxQuery(string orderid, string qrcodetype)
        {
            throw new NotImplementedException();
        }
    }

    /// <summary>
    /// IOC容器帮助类
    /// </summary>
    public partial class IocHelper
    {
        #region 接口对象
        /// <summary>
        /// ConcurrentDictionary线程安全的，Dictionary线程不安全需要自己实现，此处使用线程安全的
        /// </summary>
        private static ConcurrentDictionary<Type, object> _dic = new ConcurrentDictionary<Type, object>();
        #endregion
        /// <summary>
        /// 获取实例
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <returns></returns>
        public T Get<T>()
        {
            Type type = typeof(T);
            object obj = _dic.GetOrAdd(type, key => Activator.CreateInstance(type));
            return (T)obj;
        }
        /// <summary>
        /// 获取实例
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="func">通过Func获取实例</param>
        /// <returns></returns>
        public static T Get<T>(Func<T> func)
        {
            Type type = typeof(T);
            object obj = _dic.GetOrAdd(type, (key) => func());
            return (T)obj;
        }
        /// <summary>
        /// 注册程序集
        /// </summary>
        /// <param name="type">程序集中的一个类型</param>
        public static void RegisterAssembly(Type type)
        {
            RegisterAssembly(Assembly.GetAssembly(type).FullName);
        }
        /// <summary>
        /// 注册程序集
        /// </summary>
        /// <param name="assemblyString"></param>
        public static void RegisterAssembly(string assemblyString)
        {
            Assembly assembly = Assembly.Load(assemblyString);
            Type[] typeArr = assembly.GetTypes();
            string iServiceInterfaceName = typeof(IService).FullName;
            foreach (Type type in typeArr)
            {
                Type typeIService = type.GetInterface(iServiceInterfaceName);
                if (typeIService != null && !type.IsAbstract)
                {
                    Type[] interfaceTypeArr = type.GetInterfaces();
                    object obj = Activator.CreateInstance(type);
                    _dic.GetOrAdd(type, obj);

                    foreach (Type interfaceType in interfaceTypeArr)
                    {
                        if (interfaceType != typeof(IService))
                        {
                            _dic.GetOrAdd(interfaceType, obj);
                        }
                    }
                }
            }
        }
    }
}
